<template>
  <div class="map-container">
    <div id="container"></div>
    <!-- 用于显示鼠标坐标的元素 -->
    <div class="coordinates-display">
      <h4>🖱️ 鼠标坐标</h4>
      <div id="mouse-coords">经度: {{ lnglatLng }}, 纬度: {{ lnglatLat }}</div>
      <div id="map-zoom">缩放级别: {{ zoomLevel }}</div>
    </div>
  </div>
</template>

<script setup lang="ts">
/**
 * Canvas2D: Multiple readback operations using getImageData are faster with the willReadFrequently attribute set to true.
 *  不是致命错误，而是 浏览器性能提示（Warning），来自 Chrome 的 Canvas2D 渲染引擎。
 *  它提示你：高德地图内部多次使用 getImageData 读取像素数据，建议你为相关 <canvas> 元素加上 willReadFrequently: true 属性，以提升性能
 */
if ("HTMLCanvasElement" in globalThis) {
  const original = HTMLCanvasElement.prototype.getContext;
  HTMLCanvasElement.prototype.getContext = function (
    this: HTMLCanvasElement,
    type: string,
    options?: any
  ): any {
    if (type === "2d") {
      options = Object.assign({}, options, { willReadFrequently: true });
    }
    return original.call(this, type, options);
  } as any;
}
import { onMounted, onUnmounted, ref, defineExpose, defineEmits } from "vue";
import AMapLoader from "@amap/amap-jsapi-loader";
import type { CircleData } from "../types/index";

// 父组件传入的参数
const props = defineProps({
  lnglatLng: {
    type: String,
    default: "--",
  },
  lnglatLat: {
    type: String,
    default: "--",
  },
  radius: {
    type: String,
    default: "--",
  },
});

// 定义事件
const emit = defineEmits<{
  "coordinate-change": [lng: string, lat: string];
}>();

let map: any = null;
let tempPin: any = null;
let AMapInstance: any = null; // 存储AMap实例，以便在其他函数中使用
const lnglatLng = ref(props.lnglatLng); // 经度
const lnglatLat = ref(props.lnglatLat); // 纬度
const zoomLevel = ref("--"); // 缩放级别

// 存储绘制的圆形数据
const circles: CircleData[] = [];

// 区域计数器
let areaCounter = 0;

onMounted(() => {
  initMap();
});

onUnmounted(() => {
  // 清理临时图钉
  if (tempPin) {
    map?.remove(tempPin);
    tempPin = null;
  }
  // 销毁地图实例
  map?.destroy();
  map = null;
  AMapInstance = null;
});

/**
 * 初始化地图
 */
function initMap() {
  AMapLoader.load({
    key: "3ca10821ba8f3b1b51c490ea9db94824", // 申请好的Web端开发者Key，首次调用 load 时必填
    version: "2.0", // 指定要加载的 JSAPI 的版本，缺省时默认为 1.4.15
    plugins: [], // 需要使用的的插件列表，如比例尺'AMap.Scale'等
  })
    .then((AMap) => {
      AMapInstance = AMap; // 保存AMap实例
      map = new AMap.Map("container", {
        // 设置地图容器id
        zoom: 13, // 初始化地图级别
        center: [121.473701, 31.230416], // 初始化地图中心点位置
        viewMode: "3D", // 是否为3D地图模式
        mapStyle: "amap://styles/normal",
      });

      // 监听鼠标移动事件
      map.on("mousemove", function (e: any) {
        console.log(e.lnglat, "=========e.lnglat=========");
        // 确保lnglat对象存在且有效
        if (
          e &&
          e.lnglat &&
          e.lnglat.lng !== undefined &&
          e.lnglat.lat !== undefined
        ) {
          lnglatLng.value = e.lnglat.lng.toFixed(6);
          lnglatLat.value = e.lnglat.lat.toFixed(6);
        }
      });

      // 监听鼠标点击事件
      map.on("click", function (e: any) {
        setCenterFromClick(e.lnglat);
      });

      // 监听地图缩放事件
      map.on("zoomchange", function () {
        zoomLevel.value = map.getZoom();
      });

      zoomLevel.value = map.getZoom();
      console.log("地图初始化完成");
    })
    .catch((e) => {
      console.error("地图加载失败:", e);
      console.log("错误详情:", JSON.stringify(e));
    });
}

/**
 * 通过鼠标点击设置中心点（显示临时图钉）
 * @param lnglat
 */
function setCenterFromClick(lnglat: any) {
  // 移除之前的临时图钉
  if (tempPin) {
    map.remove(tempPin);
  }

  // 创建新的临时图钉
  tempPin = new AMapInstance.Marker({
    position: [lnglat.lng, lnglat.lat],
    content: '<div class="temp-pin"></div>',
    offset: new AMapInstance.Pixel(-12, -24),
  });

  map.add(tempPin);

  // 更新坐标输入框
  lnglatLng.value = lnglat.lng.toFixed(6);
  lnglatLat.value = lnglat.lat.toFixed(6);

  // 发送事件到父组件
  emit("coordinate-change", lnglatLng.value, lnglatLat.value);

  console.log(
    `临时图钉已设置: (${lnglat.lng.toFixed(6)}, ${lnglat.lat.toFixed(6)})`
  );
}

/**
 * 绘制圆形 - TypeScript实现
 * @param lng
 * @param lat
 * @param radius
 */
function drawCircle(lng: number, lat: number, radius: number): void {
  // 参数验证
  if (isNaN(lng) || isNaN(lat) || isNaN(radius)) {
    console.error("无效的参数：请提供有效的经度、纬度和半径值");
    alert("请先设置有效的坐标和半径值！");
    return;
  }

  if (radius <= 0) {
    console.error("无效的半径值：半径必须大于0");
    alert("半径必须大于0！");
    return;
  }

  // 确保地图实例已初始化
  if (!map || !AMapInstance) {
    console.error("地图实例尚未初始化");
    alert("地图尚未完全加载，请稍后再试！");
    return;
  }

  areaCounter++;

  // 创建圆形
  const circle = new AMapInstance.Circle({
    center: [lng, lat],
    radius: radius,
    strokeColor: "#4CAF50",
    strokeWeight: 2,
    strokeOpacity: 0.8,
    fillColor: "#4CAF50",
    fillOpacity: 0.2,
    strokeStyle: "solid",
    zIndex: 50,
  });

  // 添加到地图
  map.add(circle);

  // 添加中心点标记
  const marker = new AMapInstance.Marker({
    position: [lng, lat],
    content: `<div style="background:#4CAF50;color:white;padding:4px 8px;border-radius:12px;font-size:12px;font-weight:bold;">${areaCounter}</div>`,
    offset: new AMapInstance.Pixel(-15, -15),
  });
  map.add(marker);

  // 存储圆形数据 - 添加明确的类型注解
  const circleData: CircleData = {
    id: areaCounter,
    circle: circle,
    marker: marker,
    center: [lng, lat],
    radius: radius,
    name: `区域${areaCounter}`,
  };

  // 使用类型断言确保TypeScript正确识别类型
  circles.push(circleData as CircleData);

  // 移除临时图钉
  if (tempPin) {
    map.remove(tempPin);
    tempPin = null;
  }

  // 自动调整视图
  map.setFitView([circle]);

  console.log(
    `圆形区域${areaCounter}已绘制：中心点(${lng.toFixed(6)}, ${lat.toFixed(
      6
    )})，半径${radius}米`
  );
}

/**
 * 重置地图 - TypeScript实现
 */
function resetMap(): void {
  if (confirm("确定要重置地图吗？所有标记将被清除！")) {
    // 确保地图实例已初始化
    if (!map) {
      console.error("地图实例尚未初始化");
      return;
    }

    // 清除所有圆形和标记
    circles.forEach((circleData) => {
      map.remove(circleData.circle);
      map.remove(circleData.marker);
    });

    // 清空circles数组（由于是const声明，不能直接重新赋值）
    while (circles.length > 0) {
      circles.pop();
    }

    areaCounter = 0;

    // 移除临时图钉
    if (tempPin) {
      map.remove(tempPin);
      tempPin = null;
    }

    // 重置地图视图
    map.setZoomAndCenter(13, [121.473701, 31.230416]);

    // 清空组件中的坐标数据
    lnglatLng.value = "";
    lnglatLat.value = "";

    console.log("地图已重置");
  }
}

/**
 * 暴露方法给父组件
 */
defineExpose({
  drawCircle,
  resetMap,
});
</script>

<style lang="scss" scoped>
.map-container {
  width: 100%;
  height: 100%;
  position: relative;
  #container {
    width: 100%;
    height: 100%;
    //background: red;
  }
  .coordinates-display {
    position: absolute;
    bottom: 20px;
    left: 20px;
    background: rgba(255, 255, 255, 0.95);
    padding: 12px 16px;
    border-radius: 8px;
    box-shadow: 0 2px 10px rgba(0, 0, 0, 0.2);
    font-size: 12px;
    color: #333;
    z-index: 1000;
    min-width: 220px;
    h4 {
      margin-bottom: 8px;
      color: #4caf50;
      font-size: 14px;
    }
    div {
      margin: 4px 0;
    }
  }
}
</style>

<style lang="scss">
// 临时图钉样式
.temp-pin {
  width: 24px;
  height: 24px;
  background: #ff6b6b;
  border: 2px solid white;
  border-radius: 50% 50% 50% 0;
  transform: rotate(-45deg);
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.3);
  z-index: 1000;
  position: relative;
}

.temp-pin::after {
  content: "";
  position: absolute;
  top: 50%;
  left: 50%;
  width: 8px;
  height: 8px;
  background: white;
  border-radius: 50%;
  transform: translate(-50%, -50%) rotate(45deg);
}
</style>
